<?php

namespace app\modules\merchant\services;

use app\common\services\BaseService;
use app\components\pagination\Pagination;
use app\config\Constants;
use app\models\GoodsOrder;
use app\modules\merchant\forms\order\AdjustForm;
use app\utils\QueueUtil;
use Carbon\Carbon;

class GoodsOrderService extends BaseService{

    /**
     * 搜索
     * @param $merchant_id
     * @param $order_no
     * @param $pay_method
     * @param $status
     * @param $pay_status
     * @param $is_adjust
     * @param $start_time
     * @param $end_time
     * @param $page
     * @param $pagesize
     * @return array|\yii\db\ActiveRecord[]
     */
    public static function search($merchant_id,$order_no,$pay_method,$status,$pay_status,$is_adjust,$start_time,$end_time,&$page,$pagesize){
        $query = GoodsOrder::find()->asArray(true)
            ->orderBy(['order_id'=>SORT_DESC]);

        if(!empty($merchant_id)){
            $query->andWhere(['merchant_id'=>$merchant_id]);
        }
        if(!empty($order_no)){
            $query->andWhere(['like','order_no',$order_no]);
        }
        if(!empty($pay_method)){
            $query->andWhere(['pay_method'=>$pay_method]);
        }
        if(!empty($status)){
            $query->andWhere(['status'=>$status]);
        }
        if(!empty($pay_status)){
            $query->andWhere(['pay_status'=>$pay_status]);
        }
        if(!empty($is_adjust)){
            $query->andWhere(['is_adjust'=>$is_adjust]);
        }
        if(!empty($start_time)){
            $query->andWhere(['>=',"date_format(add_time,'%Y-%m-%d')",$start_time]);
        }
        if(!empty($end_time)){
            $query->andWhere(['<=',"date_format(add_time,'%Y-%m-%d')",$end_time]);
        }

        $page = new Pagination(['totalCount' => $query->count(), 'pageSize' => $pagesize]);
        $query->offset($page->getOffset());
        $query->limit($page->getLimit());
        $data = $query->all();

        foreach($data as $k=>$v){
            if($v['status'] == Constants::ORDER_ADJUST || $v['is_adjust'] == 2){
                $data[$k]['credentials'] = GoodsOrderCredentialService::getInfoById($merchant_id,$v['order_id']);
            }
        }

        return $data;
    }

    /**
     * 获取信息
     * @param $merchant_id
     * @param $id
     * @return array|null
     */
    public static function getInfoById($merchant_id,$id){
        $model = GoodsOrder::find()
            ->asArray(true)
            ->andWhere(['merchant_id'=>$merchant_id,'order_id'=>$id])
            ->one();
        if(!$model){
            return null;
        }
        if($model['status'] == Constants::ORDER_ADJUST || $model['is_adjust'] == 2){
            $model['credentials'] = GoodsOrderCredentialService::getInfoById($merchant_id,$id);
        }

        return $model;
    }

    /**
     * 接受
     * @param $merchant_id
     * @param $order_id
     * @return bool
     * @throws \Throwable
     * @throws \yii\db\StaleObjectException
     */
    public static function accept($merchant_id,$order_id){
        $model = GoodsOrder::findOne(['merchant_id'=>$merchant_id,'order_id'=>$order_id]);
        if(!$model){
            self::setError(\Yii::t("app","订单不存在"));
            return false;
        }
        if($model->status != Constants::ORDER_WAIT){
            self::setError(\Yii::t("app","订单状态错误"));
            return false;
        }

        $model->setAttribute("status",Constants::ORDER_ACCEPT);
        return $model->update() !== false && QueueUtil::fanout(Constants::MSG_TYPE_ORDER,Constants::ORDER_ACCEPT,['order_no'=>$model->order_no]);
    }

    /**
     * 取消
     * @param $merchant_id
     * @param $order_id
     * @return bool
     * @throws \Throwable
     * @throws \yii\db\StaleObjectException
     */
    public static function cancel($merchant_id,$order_id){
        $model = GoodsOrder::findOne(['merchant_id'=>$merchant_id,'order_id'=>$order_id]);
        if(!$model){
            self::setError(\Yii::t("app","订单不存在"));
            return false;
        }
        if(in_array($model->status,[Constants::ORDER_CANCEL,Constants::ORDER_COMPLETE,Constants::ORDER_ADJUST])){
            self::setError(\Yii::t("app","订单状态错误"));
            return false;
        }

        $model->setAttribute("status",Constants::ORDER_CANCEL);
        $model->setAttribute("pay_status",Constants::PAY_STATUS_CANCEL);
        $model->setAttribute("end_time",Carbon::now()->toDateTimeString());
        return $model->update() !== false && QueueUtil::fanout(Constants::MSG_TYPE_ORDER,Constants::ORDER_CANCEL,['order_no'=>$model->order_no,'cancel'=>Constants::MERCHANT]);
    }

    /**
     * 完成
     * @param $merchant_id
     * @param $order_id
     * @return bool
     * @throws \Throwable
     * @throws \yii\db\StaleObjectException
     */
    public static function complete($merchant_id,$order_id){
        $model = GoodsOrder::findOne(['merchant_id'=>$merchant_id,'order_id'=>$order_id]);
        if(!$model){
            self::setError(\Yii::t("app","订单不存在"));
            return false;
        }
        if($model->status != Constants::ORDER_ACCEPT){
            self::setError(\Yii::t("app","订单状态错误"));
            return false;
        }

        $model->setAttribute("status",Constants::ORDER_COMPLETE);
        $model->setAttribute("end_time",Carbon::now()->toDateTimeString());
        if($model->pay_method == Constants::PAY_DELIVERY){$model->setAttribute("pay_status",Constants::PAY_STATUS_SUCCESS);}

        return $model->update() !== false;
    }

    /**
     * 调单
     * @param AdjustForm $form
     * @return bool
     * @throws \Throwable
     * @throws \yii\db\Exception
     * @throws \yii\db\StaleObjectException
     */
    public static function adjust(AdjustForm $form){
        if(!$form->validate()){
            self::setError($form->getFirstFieldError());
            return false;
        }

        $model = GoodsOrder::findOne(['merchant_id'=>$form->merchant_id,'order_id'=>$form->order_id]);
        if(!$model){
            self::setError(\Yii::t("app","订单不存在"));
            return false;
        }
        if($model->status != Constants::ORDER_COMPLETE){
            self::setError(\Yii::t("app","订单状态错误"));
            return false;
        }

        $transaction = \Yii::$app->getDb()->beginTransaction();

        if(!GoodsOrderCredentialService::create($form)){
            $transaction->rollBack();
            return false;
        }

        $model->setAttribute("status",Constants::ORDER_ADJUST);
        if($model->update() === false){
            $transaction->rollBack();
            return false;
        }
        $transaction->commit();
        return true;
    }

    /**
     * 重新打印
     * @param $merchant_id
     * @param $id
     * @return bool
     * @throws \yii\base\InvalidConfigException
     */
    public static function repeatPrint($merchant_id,$id){
        $model = GoodsOrder::findOne(['merchant_id'=>$merchant_id,'order_id'=>$id]);
        if(!$model){
            self::setError(\Yii::t("订单不存在"));
            return false;
        }

        return QueueUtil::fanout(Constants::MSG_TYPE_ORDER,Constants::EVENT_TYPE_ORDER_REPEAT_PRINT,['order_no'=>$model->order_no]);
    }
}